package me.itsoo.artemis.framework.core.util;

import lombok.AccessLevel;
import lombok.NoArgsConstructor;
import me.itsoo.artemis.framework.core.exception.CloseIoStreamException;

import java.io.Closeable;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.io.OutputStreamWriter;
import java.io.Reader;
import java.nio.charset.Charset;
import java.nio.charset.StandardCharsets;
import java.sql.Connection;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;

/**
 * IoUtils
 *
 * @author zxy
 * @version 0.0.1
 * @since 2023/5/19
 */
@NoArgsConstructor(access = AccessLevel.PRIVATE)
public class IoUtils {

    /**
     * 获取 OutputStreamWriter
     *
     * @param out     OutputStream
     * @param charset Charset
     * @return OutputStreamWriter
     */
    public static OutputStreamWriter getWriter(OutputStream out, Charset charset) {
        if (out == null) {
            return null;
        }

        return (charset == null) ? new OutputStreamWriter(out) : new OutputStreamWriter(out, charset);
    }

    /**
     * 流写出去
     *
     * @param out      OutputStream
     * @param contents Object[]
     */
    public static void write(OutputStream out, Object... contents) {
        write(out, StandardCharsets.UTF_8, contents);
    }

    /**
     * 流写出去
     *
     * @param out      OutputStream
     * @param charset  charset
     * @param contents Object[]
     */
    public static void write(OutputStream out, Charset charset, Object... contents) {
        try (OutputStreamWriter osw = getWriter(out, charset)) {
            if (osw != null) {
                for (Object content : contents) {
                    if (content != null) {
                        osw.write(content.toString());
                    }
                }
                osw.flush();
            }
        } catch (IOException e) {
            throw new CloseIoStreamException();
        }
    }

    /**
     * 关闭资源
     *
     * @param is InputStream
     */
    public static void close(InputStream is) {
        if (is != null) {
            try {
                is.close();
            } catch (IOException e) {
                throw new CloseIoStreamException();
            }
        }
    }

    /**
     * 关闭资源
     *
     * @param reader Reader
     */
    public static void close(Reader reader) {
        if (reader != null) {
            try {
                reader.close();
            } catch (IOException e) {
                throw new CloseIoStreamException();
            }
        }
    }

    /**
     * 关闭资源
     *
     * @param conn Connection
     */
    public static void close(Connection conn) {
        if (conn != null) {
            try {
                conn.close();
            } catch (SQLException e) {
                throw new CloseIoStreamException();
            }
        }
    }

    /**
     * 关闭资源
     *
     * @param stmt Statement
     */
    public static void close(Statement stmt) {
        if (stmt != null) {
            try {
                stmt.close();
            } catch (SQLException e) {
                throw new CloseIoStreamException();
            }
        }
    }

    /**
     * 关闭资源
     *
     * @param rs ResultSet
     */
    public static void close(ResultSet rs) {
        if (rs != null) {
            try {
                rs.close();
            } catch (SQLException e) {
                throw new CloseIoStreamException();
            }
        }
    }

    /**
     * 关闭资源
     *
     * @param closeable Closeable
     */
    public static void close(Closeable closeable) {
        if (closeable != null) {
            try {
                closeable.close();
            } catch (Exception ignore) {
                throw new CloseIoStreamException();
            }
        }
    }
}
